﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using UnityEngine;

/// <summary>
/// 本地持久保存资源管理器(热更新资源)
/// </summary>
public class PersistentDataMgr : SingletonAuto<PersistentDataMgr>
{
    /// <summary>
    /// 应用内部数据路径(这个路径只读)
    /// </summary>
    public static string AppContentPath
    {
        get
        {
            string path = string.Empty;
            switch (Application.platform)
            {
                case RuntimePlatform.Android:
                    path = "jar:file://" + Application.dataPath + "!/assets/";
                    break;
                case RuntimePlatform.IPhonePlayer:
                    path = Application.dataPath + "/Raw/";
                    break;
                default:
                    path = Application.dataPath + "/StreamingAssets/";
                    break;
            }
            return path;
        }
    }
    /// <summary>
    /// 取得数据存放目录(热更资源下载目录)
    /// </summary>
    public static string DataPath
    {
        get
        {
            if (Application.isMobilePlatform)
            {
                return Application.persistentDataPath;
            }
            if (Application.platform == RuntimePlatform.OSXEditor)
            {
                int i = Application.dataPath.LastIndexOf('/');
                return Application.dataPath.Substring(0, i + 1);
            }

            return Application.persistentDataPath;
        }
    }

    private const string streamAssetVersionFile = "UVersion"; // 解压版本号文件名
    private const string assetBundleRootPath = "ABs"; // 存放目录名
    public const string assetBundleExtName = "ab"; // 扩展名

    private MonoBehaviour driver;
    private Action unPackageCallback;
    /// <summary>
    /// 需要用到协程，搞个驱动进来
    /// </summary>
    /// <param name="setup"></param>
    public void SetMono(MonoBehaviour setup)
    {
        driver = setup;
    }

    public void CheckAndUnPackage(Action callback)
    {
        unPackageCallback = callback;
        // 是否已经解包
        if ( File.Exists(Path.Combine(Application.persistentDataPath, streamAssetVersionFile)) )
        {
            Debug.LogWarning("已解包");
            unPackageCallback();
            return;
        }

        Debug.LogWarning("解包中。。。");
        driver.StartCoroutine(unpackage());
    }

    /// <summary>
    /// 解包
    /// </summary>
    IEnumerator unpackage()
    {
        var outfile = Path.Combine(DataPath, assetBundleRootPath);
        var resPath = Path.Combine(AppContentPath, assetBundleRootPath);
        string[] fileList = Directory.GetFiles(resPath, "*." + assetBundleExtName, SearchOption.AllDirectories);
        if (Application.platform == RuntimePlatform.Android)
        {
            foreach (var fliePath in fileList)
            {
                WWW www = new WWW(fliePath);
                yield return www;

                if (www.isDone)
                {
                    File.WriteAllBytes(outfile, www.bytes);
                }
            }
        }
        else
        {
            CopyFiles(resPath, outfile);
        }
        // 创建解包版本标记
        //File.CreateText(Path.Combine(Application.persistentDataPath, streamAssetVersionFile));

        Debug.LogWarning("解包完毕，目录：" + Application.persistentDataPath);
        unPackageCallback();
    }

    public static void CopyFiles(string sourceDir, string destDir, string searchPattern = "*.*", SearchOption option = SearchOption.AllDirectories)
    {
        if (!Directory.Exists(sourceDir))
        {
            return;
        }

        string[] files = Directory.GetFiles(sourceDir, searchPattern, option);
        int len = sourceDir.Length;

        if (sourceDir[len - 1] == '/' || sourceDir[len - 1] == '\\')
        {
            --len;
        }

        for (int i = 0; i < files.Length; i++)
        {
            string str = files[i].Remove(0, len);
            string dest = destDir + "/" + str;
            string dir = Path.GetDirectoryName(dest);
            Directory.CreateDirectory(dir);
            File.Copy(files[i], dest, true);
        }
    }

}
